/*   1:    */ package org.intellij.plugins.relaxNG.model.resolve;
/*   2:    */ 
/*   3:    */

import com.intellij.openapi.util.Factory;
import com.intellij.openapi.util.Key;
import com.intellij.openapi.util.ModificationTracker;
import com.intellij.psi.PsiElement;
import com.intellij.psi.PsiFile;
import com.intellij.psi.search.PsiElementProcessor;
import com.intellij.psi.util.CachedValue;
import com.intellij.psi.util.CachedValueProvider;
import com.intellij.psi.util.CachedValueProvider.Result;
import com.intellij.psi.util.CachedValuesManager;
import com.intellij.psi.xml.XmlFile;
import com.intellij.util.containers.ContainerUtil;
import com.intellij.util.containers.HashSet;
import com.intellij.util.xml.DomFileElement;
import com.intellij.util.xml.DomManager;
import gnu.trove.THashSet;
import org.intellij.plugins.relaxNG.compact.psi.RncFile;
import org.intellij.plugins.relaxNG.model.*;
import org.intellij.plugins.relaxNG.xml.dom.RngGrammar;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import java.util.Collections;
import java.util.Map;
import java.util.Set;

/*   4:    */
/*   5:    */
/*   6:    */
/*   7:    */
/*   8:    */
/*   9:    */
/*  10:    */
/*  11:    */
/*  12:    */
/*  13:    */
/*  14:    */
/*  15:    */
/*  16:    */
/*  17:    */
/*  18:    */
/*  19:    */
/*  20:    */
/*  21:    */
/*  22:    */
/*  23:    */
/*  24:    */
/*  25:    */
/*  26:    */
/*  27:    */
/*  28:    */
/*  29:    */
/*  30:    */
/*  31:    */
/*  32:    */
/*  33:    */
/*  34:    */ 
/*  35:    */ public class DefinitionResolver
/*  36:    */   extends CommonElement.Visitor
/*  37:    */   implements CachedValueProvider<Map<String, Set<Define>>>, Factory<Set<Define>>
/*  38:    */ {
/*  39: 52 */   private static final Key<CachedValue<Map<String, Set<Define>>>> a = Key.create("CACHED_DEFINES");
/*  40: 54 */   private static final ThreadLocal<Set<PsiFile>> b = new ThreadLocal();
/*  41: 55 */   private static final ThreadLocal<Map<String, Set<Define>>> c = new ThreadLocal()
/*  42:    */   {
/*  43:    */     protected Map<String, Set<Define>> initialValue()
/*  44:    */     {
/*  45: 58 */       return ContainerUtil.newHashMap();
/*  46:    */     }
/*  47:    */   };
/*  48:    */   private final Grammar d;
/*  49:    */   
/*  50:    */   private DefinitionResolver(Grammar paramGrammar)
/*  51:    */   {
/*  52: 65 */     this.d = paramGrammar;
/*  53:    */   }
/*  54:    */   
/*  55:    */   public void visitInclude(Include paramInclude)
/*  56:    */   {
/*  57: 70 */     paramInclude.acceptChildren(this);
/*  58:    */     
/*  59: 72 */     PsiFile localPsiFile = paramInclude.getInclude();
/*  60: 73 */     if (b.get() == null) {
/*  61: 74 */       b.set(ContainerUtil.newIdentityTroveSet());
/*  62:    */     }
/*  63: 76 */     if ((localPsiFile != null) && (((Set)b.get()).add(localPsiFile))) {
/*  64: 77 */       a(localPsiFile, this);
/*  65:    */     }
/*  66:    */   }
/*  67:    */   
/*  68:    */   private static void a(PsiFile paramPsiFile, CommonElement.Visitor paramVisitor)
/*  69:    */   {
/*  70:    */     Object localObject;
/*  71: 82 */     if ((paramPsiFile instanceof RncFile))
/*  72:    */     {
/*  73: 83 */       localObject = ((RncFile)paramPsiFile).getGrammar();
/*  74: 84 */       if (localObject != null) {
/*  75: 85 */         ((Grammar)localObject).acceptChildren(paramVisitor);
/*  76:    */       }
/*  77:    */     }
/*  78: 87 */     else if ((paramPsiFile instanceof XmlFile))
/*  79:    */     {
/*  80: 88 */       localObject = DomManager.getDomManager(paramPsiFile.getProject());
/*  81: 89 */       DomFileElement localDomFileElement = ((DomManager)localObject).getFileElement((XmlFile)paramPsiFile, RngGrammar.class);
/*  82: 90 */       if (localDomFileElement != null) {
/*  83: 91 */         ((RngGrammar)localDomFileElement.getRootElement()).acceptChildren(paramVisitor);
/*  84:    */       }
/*  85:    */     }
/*  86:    */   }
/*  87:    */   
/*  88:    */   public void visitDiv(Div paramDiv)
/*  89:    */   {
/*  90: 98 */     paramDiv.acceptChildren(this);
/*  91:    */   }
/*  92:    */   
/*  93:    */   public void visitDefine(Define paramDefine)
/*  94:    */   {
/*  95:103 */     ((Set)ContainerUtil.getOrCreate((Map)c.get(), paramDefine.getName(), this)).add(paramDefine);
/*  96:    */   }
/*  97:    */   
/*  98:    */   public void visitPattern(Pattern paramPattern) {}
/*  99:    */   
/* 100:    */   public void visitGrammar(Grammar paramGrammar) {}
/* 101:    */   
/* 102:    */   public void visitRef(Ref paramRef) {}
/* 103:    */   
/* 104:    */   public Set<Define> create()
/* 105:    */   {
/* 106:117 */     return new THashSet();
/* 107:    */   }
/* 108:    */   
/* 109:    */   public CachedValueProvider.Result<Map<String, Set<Define>>> compute()
/* 110:    */   {
/* 111:    */     try
/* 112:    */     {
/* 113:122 */       this.d.acceptChildren(this);
/* 114:    */       
/* 115:124 */       PsiElement localPsiElement = this.d.getPsiElement();
/* 116:125 */       if ((localPsiElement == null) || (!localPsiElement.isValid())) {
/* 117:126 */         return CachedValueProvider.Result.create(null, new Object[] { ModificationTracker.EVER_CHANGED });
/* 118:    */       }
/* 119:129 */       Object localObject1 = localPsiElement.getContainingFile();
/* 120:    */       CachedValueProvider.Result localResult;
/* 121:130 */       if (b.get() != null)
/* 122:    */       {
/* 123:131 */         ((Set)b.get()).add(localObject1);
/* 124:132 */         return CachedValueProvider.Result.create(c.get(), ((Set)b.get()).toArray());
/* 125:    */       }
/* 126:134 */       return CachedValueProvider.Result.create(c.get(), new Object[] { localObject1 });
/* 127:    */     }
/* 128:    */     finally
/* 129:    */     {
/* 130:137 */       b.remove();
/* 131:138 */       c.remove();
/* 132:    */     }
/* 133:    */   }
/* 134:    */   
/* 135:    */   @Nullable
/* 136:    */   public static Set<Define> resolve(Grammar paramGrammar, String paramString)
/* 137:    */   {
/* 138:144 */     Map localMap = getAllVariants(paramGrammar);
/* 139:145 */     if (localMap == null) {
/* 140:146 */       return null;
/* 141:    */     }
/* 142:149 */     Set localSet = (Set)localMap.get(paramString);
/* 143:152 */     if ((localSet == null) || (localSet.size() == 0))
/* 144:    */     {
/* 145:153 */       PsiElement localPsiElement = paramGrammar.getPsiElement();
/* 146:154 */       if (localPsiElement != null)
/* 147:    */       {
/* 148:155 */         PsiFile localPsiFile = localPsiElement.getContainingFile();
/* 149:156 */         if ((localPsiFile instanceof XmlFile))
/* 150:    */         {
/* 151:157 */           BackwardDefinitionResolver localBackwardDefinitionResolver = new BackwardDefinitionResolver(paramString);
/* 152:158 */           RelaxIncludeIndex.processBackwardDependencies((XmlFile)localPsiFile, localBackwardDefinitionResolver);
/* 153:159 */           return localBackwardDefinitionResolver.getResult();
/* 154:    */         }
/* 155:    */       }
/* 156:    */     }
/* 157:164 */     return localSet;
/* 158:    */   }
/* 159:    */   
/* 160:    */   @Nullable
/* 161:    */   public static Map<String, Set<Define>> getAllVariants(Grammar paramGrammar)
/* 162:    */   {
/* 163:169 */     PsiElement localPsiElement = paramGrammar.getPsiElement();
/* 164:170 */     if ((localPsiElement == null) || (!localPsiElement.isValid())) {
/* 165:170 */       return null;
/* 166:    */     }
/* 167:172 */     CachedValuesManager localCachedValuesManager = CachedValuesManager.getManager(localPsiElement.getProject());
/* 168:173 */     CachedValue localCachedValue = (CachedValue)localPsiElement.getUserData(a);
/* 169:174 */     if ((localCachedValue == null) || (!((DefinitionResolver)localCachedValue.getValueProvider()).a()))
/* 170:    */     {
/* 171:175 */       DefinitionResolver localDefinitionResolver = new DefinitionResolver(paramGrammar);
/* 172:176 */       localCachedValue = localCachedValuesManager.createCachedValue(localDefinitionResolver, false);
/* 173:177 */       localPsiElement.putUserData(a, localCachedValue);
/* 174:    */     }
/* 175:179 */     return (Map)localCachedValue.getValue();
/* 176:    */   }
/* 177:    */   
/* 178:    */   private boolean a()
/* 179:    */   {
/* 180:183 */     PsiElement localPsiElement = this.d.getPsiElement();
/* 181:184 */     return (localPsiElement != null) && (localPsiElement.isValid());
/* 182:    */   }
/* 183:    */   
/* 184:    */   private static class BackwardDefinitionResolver
/* 185:    */     implements PsiElementProcessor<XmlFile>
/* 186:    */   {
/* 187:    */     private final String a;
/* 188:    */     private Define b;
/* 189:190 */     private final Set<PsiFile> c = new HashSet();
/* 190:    */     
/* 191:    */     public BackwardDefinitionResolver(String paramString)
/* 192:    */     {
/* 193:193 */       this.a = paramString;
/* 194:    */     }
/* 195:    */     
/* 196:    */     public boolean execute(@NotNull XmlFile paramXmlFile)
/* 197:    */     {
/* 198:197 */       if (paramXmlFile == null) {
/* 199:197 */         throw new IllegalArgumentException(String.format("Argument %s for @NotNull parameter of %s.%s must not be null", new Object[] { "0", "org/intellij/plugins/relaxNG/model/resolve/DefinitionResolver$BackwardDefinitionResolver", "execute" }));
/* 200:    */       }
/* 201:197 */       Grammar localGrammar = GrammarFactory.getGrammar(paramXmlFile);
/* 202:198 */       if (localGrammar != null) {
/* 203:199 */         localGrammar.acceptChildren(new CommonElement.Visitor()
/* 204:    */         {
/* 205:    */           public void visitElement(CommonElement paramAnonymousCommonElement)
/* 206:    */           {
/* 207:202 */             if (DefinitionResolver.BackwardDefinitionResolver.this.b == null) {
/* 208:203 */               super.visitElement(paramAnonymousCommonElement);
/* 209:    */             }
/* 210:    */           }
/* 211:    */           
/* 212:    */           public void visitDefine(Define paramAnonymousDefine)
/* 213:    */           {
/* 214:209 */             if (DefinitionResolver.BackwardDefinitionResolver.this.a.equals(paramAnonymousDefine.getName())) {
/* 215:210 */               DefinitionResolver.BackwardDefinitionResolver.this.b = paramAnonymousDefine;
/* 216:    */             }
/* 217:    */           }
/* 218:    */           
/* 219:    */           public void visitInclude(Include paramAnonymousInclude)
/* 220:    */           {
/* 221:216 */             PsiFile localPsiFile = paramAnonymousInclude.getInclude();
/* 222:217 */             if ((localPsiFile != null) && (DefinitionResolver.BackwardDefinitionResolver.this.c.add(localPsiFile))) {
/* 223:218 */               DefinitionResolver.a(localPsiFile, this);
/* 224:    */             }
/* 225:    */           }
/* 226:    */         });
/* 227:    */       }
/* 228:223 */       return this.b == null;
/* 229:    */     }
/* 230:    */     
/* 231:    */     @Nullable
/* 232:    */     public Set<Define> getResult()
/* 233:    */     {
/* 234:228 */       return this.b != null ? Collections.singleton(this.b) : null;
/* 235:    */     }
/* 236:    */   }
/* 237:    */ }



/* Location:           E:\idea\

 * Qualified Name:     org.intellij.plugins.relaxNG.model.resolve.DefinitionResolver

 * JD-Core Version:    0.7.0.1

 */